use gfx_backend_vulkan as b;

use winit::{
    event_loop::{EventLoop, ControlFlow},
    window::{WindowBuilder, Window},
    dpi::PhysicalSize,
    event::{Event, WindowEvent}
};
use gfx_hal::{Instance, Backend};
use gfx_hal::adapter::{ Adapter, DeviceType};

#[derive(Default)]
struct HelloTriangleApplication {
    window: Option<Window>,
    instance: Option<b::Instance>,
    physical_device: Option<>
}

impl HelloTriangleApplication {
    pub fn run(mut self) {
        let event_loop = EventLoop::new();
        self.init_window(&event_loop);
        self.init_vulkan();
        // mainLoop
        event_loop.run(move |e, _, cf| {
            *cf = ControlFlow::Poll;

            match e {
                Event::WindowEvent { event, ..} => {
                    match event {
                        WindowEvent::CloseRequested => *cf = ControlFlow::Exit,
                        _ => ()
                    }
                }
                Event::MainEventsCleared => {

                }
                _ => {}
            }
        })
    }

    fn init_window(&mut self, event_loop: &EventLoop<()>) {
        let window = WindowBuilder::new()
            .with_title("Vulkan")
            .with_inner_size(PhysicalSize::new(800, 600))
            .build(event_loop).unwrap();

        self.window = Some(window);
    }

    fn init_vulkan(&mut self) {
        self.init_instance();
    }

    fn init_instance(&mut self) {
        let instance = b::Instance::create("Hello Triangle", 1).unwrap();
        for extension in &instance.extensions {
            if let Ok(name) = extension.to_str() {
                println!("{}", name);
            }
        }
        self.instance = Some(instance);
    }

    fn pick_physical_device(&mut self) {
        let adapters = self.instance.unwrap().enumerate_adapters();
        let adapter = adapters.into_iter()
            .find(is_device_suitable)
            .unwrap();

            ()
    }
}

fn is_device_suitable(adapter: &Adapter<b::Backend>) -> bool {
    adapter.info.device_type == DeviceType::DiscreteGpu
}

fn main() {
    let app: HelloTriangleApplication = Default::default();
    app.run();
}
